/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package Dib;

import java.awt.Color;
import java.awt.Graphics;
import java.awt.event.*;
import java.util.ArrayList;
import javax.swing.*;
import ia.*;
import java.util.Stack;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableModel;

/**
 *
 * @author alex
 */
public class Lienzo extends JPanel implements MouseListener{

    int contador=0;
    ArrayList<Nodo> nodos;
    Boolean AgregandoNodos=false;
    Boolean AgregandoAristas=false;
    int tipoAlgoritmo;
    public final static int CostoUniforme=1;
    public final static int BusquedaEnProfundidad=2;
    public final static int BusquedaEnAnchura=3;
    public final static int PrimeroElMejor=4;
    public final static int AEstrella=5;
    JPopupMenu clickDerechoNodo;
    
    public void InicializarMenu(JPopupMenu menu)
    {
        this.clickDerechoNodo= menu;
    }
    

    public int getTipoAlgoritmo() {
        return tipoAlgoritmo;
    }

    public void setTipoAlgoritmo(int tipoAlgoritmo) {
        this.tipoAlgoritmo = tipoAlgoritmo;
    }
    

    public Boolean getAgregandoAristas() {
        return AgregandoAristas;
    }

    public void setAgregandoAristas(Boolean AgregandoAristas) {
        this.AgregandoAristas = AgregandoAristas;
    }
    
    
    public Boolean getAgregandoNodos() {
        return AgregandoNodos;
    }

    public void setAgregandoNodos(Boolean AgregandoNodos) {
        this.AgregandoNodos = AgregandoNodos;
    }
    
    
    public Lienzo() {
    nodos= new ArrayList<Nodo>();
    this.addMouseListener(this);
    MouseMotionAdapter adap= new MouseMotionAdapter() 
    {

            @Override
            public void mouseMoved(MouseEvent e) {
                super.mouseMoved(e);
                if(AgregandoAristas)
                {
                    if(a!=null)
                    {
                        a.setPosxf(e.getX());
                        a.setPosyf(e.getY());
                        a.repaint();
                        repaint();
                    }
                }
            }
        
    };
    this.addMouseMotionListener(adap);
    KeyAdapter adapk= new KeyAdapter() 
    {

            @Override
            public void keyPressed(KeyEvent e) {
                super.keyPressed(e);
                if(getSelectedNode()!=null)
                {
                    JOptionPane.showMessageDialog(null, e.getKeyCode());
                }
            }
        
    };
    this.addKeyListener(adapk);
    }

   
    @Override
    protected void paintComponent (Graphics g) {
        //super.paintComponent(g);
        g.setColor(Color.white);
        g.fillRect(0, 0, this.getSize().width,this.getSize().height);
        for (Nodo nodo : nodos) {
            nodo.paintComponent(g);
        }
        if(a!=null)
            a.paint(g);
        
    }
Arista a=null;
    @Override
    public void mouseClicked(MouseEvent e) {
        this.repaint();
      if( e.getButton()==1){
        if(e.getSource().getClass() == Lienzo.class){
                a=null;
                if(this.AgregandoNodos){
                    Nodo n;
                    switch(this.tipoAlgoritmo)
                    {
                    /*Primero el mejor*/
                        case 4:
                    try {
                        n = new Nodo(e.getX(), e.getY(),true);
                        if(n.getNombre()!=null)
                        { n.addMouseListener(this);
                                this.add(n);
                                this.nodos.add(n);
                        }
                    } catch (Throwable ex) {
                        Logger.getLogger(Lienzo.class.getName()).log(Level.SEVERE, null, ex);
                    }
                          //  n.setComponentPopupMenu(clickDerechoNodo);
                              
                            break;
                            /*A estrella*/
                        case 5:
                    try {
                        n = new Nodo(e.getX(), e.getY(),true);
                         if(n.getNombre()!=null)
                        {
                            n.addMouseListener(this);
                                this.add(n);
                                this.nodos.add(n);
                        }
                    } catch (Throwable ex) {
                        Logger.getLogger(Lienzo.class.getName()).log(Level.SEVERE, null, ex);
                    }
                        //    n.setComponentPopupMenu(clickDerechoNodo);
                                
                            break;
                        default:
                    try {
                        n = new Nodo(e.getX(), e.getY());
                        if(n.getNombre()!=null)
                        {
                             n.addMouseListener(this);
                                this.add(n);
                                this.nodos.add(n);
                        }
                    } catch (Throwable ex) {
                        Logger.getLogger(Lienzo.class.getName()).log(Level.SEVERE, null, ex);
                    }
                          //  n.setComponentPopupMenu(clickDerechoNodo);
                               
                            break;
                    }

                }

            }
            if(e.getSource().getClass() == Nodo.class)
            {
                if(this.AgregandoAristas){
                if(a==null){
                    nodos.get( nodos.indexOf((Nodo) e.getSource() )).setSeleccionado(true);
                    a = new Arista(((Nodo) e.getSource() ).getPosx()+60, ((Nodo) e.getSource() ).getPosy()+30, ((Nodo) e.getSource() ).getPosx()+60, ((Nodo) e.getSource() ).getPosy()+30);
                }
                else
                {
                    Nodo an= this.getSelectedNode();
                    if( an  == ((Nodo) e.getSource()))
                    {
                        JOptionPane.showMessageDialog(this, "No se puede seleccionar el mismo nodo");
                        return;
                    }
                    if(an!=null)
                    {
                        switch(this.tipoAlgoritmo)
                        {
                            case 1:
                                try{
                                a.getValorDelCamino();
                                if(a.getValorCamino()==null)
                                    a=null;
                                }catch(Throwable et)
                                {
                                    
                                }
                                break;
                            case 5:
                                  try{
                                a.getValorDelCamino();if(a.getValorCamino()==null)
                                    a=null;}
                                catch(Throwable et2)
                                {
                                    
                                }
                                break;
                        }
                        if(an.getaDerecha()==null && a!=null){
                            a.setOrigen( ((Nodo) e.getSource()));
                            an.setaDerecha(a);
                            ((Nodo) e.getSource()).repaint();
                            an.repaint();
                            a=null;
                            this.cleanSelectedNode();
                        }
                        else if(an.getaIzquierda()==null && a!=null){
                            a.setOrigen( ((Nodo) e.getSource()));
                            an.setaIzquierda(a);
                            ((Nodo) e.getSource()).repaint();
                            an.repaint();
                            a=null;
                            this.cleanSelectedNode();
                        }
                    }
                }
                }
                if(this.AgregandoNodos)
                {
                    this.cleanSelectedNode();
                    ((Nodo) e.getSource() ).setSeleccionado(true);
                }
            }
      }
       this.repaint();
      if(e.getButton()==3)
      {
          this.cleanSelectedNode();
          if(e.getSource().getClass() == Nodo.class)
            {
                java.awt.Point p= e.getPoint();
               if(((Nodo)e.getSource()).getaDerecha()!=null||((Nodo)e.getSource()).getaIzquierda()!=null)
               {
                  ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).jMenu1.setEnabled(true);
                  ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).EditarAristaDerechaMenuItem.setEnabled(((Nodo)e.getSource()).getaDerecha()!=null);
                  ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).EliminarAristaDerechaMenuItem.setEnabled(((Nodo)e.getSource()).getaDerecha()!=null);
                  ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).EditarAristaIzquierdaMenuItem.setEnabled(((Nodo)e.getSource()).getaIzquierda()!=null);
                  ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).EliminarAristaIzquierdaMenuItem.setEnabled(((Nodo)e.getSource()).getaIzquierda()!=null);
               }
               else
               {
                   ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).jMenu1.setEnabled(false);
               }
               clickDerechoNodo.show(((Nodo)e.getSource()), e.getX(), e.getY());
               ((Nodo)e.getSource()).setSeleccionado(true);
            }
        
      }
     
    }
    private Nodo getNodoInicial()
    {
        if(this.nodos!=null)
        {
            for (Nodo nodo : nodos) {
                if(nodo.isInicio())
                    return nodo;
            }
        }
        return null;
    }
    private Nodo getNodoFinal()
    {
        if(this.nodos!=null)
        {
            for (Nodo nodo : nodos) {
                if(nodo.isFin())
                    return nodo;
            }
        }
        return null;
    }
    private void cleanSelectedNode()
    {
        if(this.nodos!=null)
        {
            for (Nodo nodo : nodos) {
                if(nodo.getSeleccionado())
                    nodo.setSeleccionado(false);
            }
        }
    }
    public void cleanNodoInicial()
    {
         if(this.nodos!=null)
        {
            for (Nodo nodo : nodos) {
                if(nodo.isInicio()==true)
                    nodo.setInicio(false);
            }
        }
    }
    public void deleteNode(Nodo n)
    {
        this.nodos.remove(n);
        repaint();
    }
    public void cleanNodoFinal()
    {
         if(this.nodos!=null)
        {
            for (Nodo nodo : nodos) {
                if(nodo.isFin()==true)
                    nodo.setFin(false);
            }
        }
    }
    public Nodo getSelectedNode()
    {
        if(this.nodos!=null)
        {
            for (Nodo nodo : nodos) {
                if(nodo.getSeleccionado())
                    return nodo;
            }
        }
        return null;
    }
    @Override
    public void mousePressed(MouseEvent e) {
       
    }

    @Override
    public void mouseReleased(MouseEvent e) {
       
    }

    @Override
    public void mouseEntered(MouseEvent e) {
       
    }

    @Override
    public void mouseExited(MouseEvent e) {
        
    }
    
   public void limpiarNodos()
   {
       this.nodos=new ArrayList<Nodo>();
       this.repaint();
   }

    public ArrayList<Nodo> getNodos() {
        return nodos;
    }
    int r=1;
    
        ArrayList<Nodo> temp=null;
        int valor=0;
        Integer cont=0;
    public int costoUniformeAlg(Nodo f,Nodo i, ArrayList<NodoCamino> ex)
    {
        if(ex==null)
        {
            cont=1;
            ex= new ArrayList<NodoCamino>();
             tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt("("+i.getNombre()+")",cont-1, 1);
            //System.out.println("("+i.getNombre()+")");
            if(i.getaDerecha()!=null&& i.getaIzquierda()!=null)
            {
                temp = new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(i.getaDerecha().getValorCamino(), i.getaDerecha().getOrigen().getNombre()+i.getNombre(),temp));
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(i.getaIzquierda().getValorCamino(), i.getaIzquierda().getOrigen().getNombre()+i.getNombre(),temp));
                return costoUniformeAlg(f, i, ex);
            }
            if(i.getaDerecha()==null&& i.getaIzquierda()!=null)
            {
              temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(i.getaIzquierda().getValorCamino(), i.getaIzquierda().getOrigen().getNombre()+i.getNombre(),temp));
                return costoUniformeAlg(f, i, ex);  
            }
            if(i.getaDerecha()!=null&& i.getaIzquierda()==null)
            {
                 temp = new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(i.getaDerecha().getValorCamino(), i.getaDerecha().getOrigen().getNombre()+i.getNombre(),temp));
                return costoUniformeAlg(f, i, ex);  
            }
            if(i.getaDerecha()==null&& i.getaIzquierda()==null)
            {
                JOptionPane.showMessageDialog(null, "Error, el nodo inicial debe de tener almenos una arista ","",JOptionPane.ERROR_MESSAGE);
                return 0;
            }
            
        }
        else
        {
            NodoCamino nMenor= ex.get(0);
            cont++;
            String nombre="";
            //System.out.println("\n-----------------------------");
            for (NodoCamino nodoCamino : ex) {
                nombre+=" ("+nodoCamino.ValorCamino+nodoCamino.NombreCamino+") ";
                if(nMenor.ValorCamino>nodoCamino.ValorCamino)
                      nMenor= nodoCamino;
                
            }
             tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt(nombre,cont-1, 1);
            Nodo toExp= nMenor.NodosCamino.get(nMenor.NodosCamino.size()-1);
            if(toExp.getaDerecha()!=null && toExp.getaIzquierda()!=null)
            {
                temp= new ArrayList<Nodo>();
                valor=0;
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                //Se agrega la expansion de la derecha
                temp.add(toExp.getaDerecha().getOrigen());
                //Se calcula el valor de la expansion de la derecha
                valor= nMenor.ValorCamino+ toExp.getaDerecha().getValorCamino();
                //Se agrega la expansion a la lista de nodos expandidos
                ex.add(new NodoCamino(valor, toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                /*Ahora vamos con la izquierda*/
                temp= new ArrayList<Nodo>();
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                valor-=toExp.getaDerecha().getValorCamino();
                valor+=toExp.getaIzquierda().getValorCamino();
                ex.add(new NodoCamino(valor, toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                //Una vez finalizamos la expasion de los nodos eliminamos el camino anterior de la lista de expandidos
                ex.remove(nMenor);
                //Se vuelve a llamar a la funcion
                costoUniformeAlg(f, i, ex);
            }
            if(toExp.getaDerecha()==null && toExp.getaIzquierda()!=null)
            {
                 temp= new ArrayList<Nodo>();
                valor=0;
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                //Se agrega la expansion de la derecha
                temp.add(toExp.getaIzquierda().getOrigen());
                //Se calcula el valor de la expansion de la derecha
                valor= nMenor.ValorCamino+ toExp.getaIzquierda().getValorCamino();
                //Se agrega la expansion a la lista de nodos expandidos
                ex.add(new NodoCamino(valor, toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                ex.remove(nMenor);
                //Se vuelve a llamar a la funcion
                costoUniformeAlg(f, i, ex);
            }
            if(toExp.getaDerecha()!=null && toExp.getaIzquierda()==null)
            {
                temp= new ArrayList<Nodo>();
                valor=0;
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                //Se agrega la expansion de la derecha
                temp.add(toExp.getaDerecha().getOrigen());
                //Se calcula el valor de la expansion de la derecha
                valor= nMenor.ValorCamino+ toExp.getaDerecha().getValorCamino();
                //Se agrega la expansion a la lista de nodos expandidos
                ex.add(new NodoCamino(valor, toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                ex.remove(nMenor);
                //Se vuelve a llamar a la funcion
                costoUniformeAlg(f, i, ex);
            }
            if(toExp.getaDerecha()==null && toExp.getaIzquierda()==null)
            {
                if(toExp==f)
                    return 1;
                else{
                    //Si no hay nada que expander y toExp no es la meta entonces el camino se elmina
                    //y se una vez se encuentra el camino eliminado se vuelve a
                    //preguntar cual es el nuevo camino mas corto
                    ex.remove(nMenor);
                    costoUniformeAlg(f, i, ex);
                }
            }
        }
        return 0;
    }
  
    VisitiadosExpandidos visited=null;
    private int primeroProfundidad(boolean visitados, Nodo i, Nodo f,Stack <NodoCamino> ex)
    {
        if(ex==null)
        {
            cont=1;
            ex= new Stack<NodoCamino>();
            if(visitados)
            {
                visited= new VisitiadosExpandidos();
                visited.add(i);
            }
             tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt("("+i.getNombre()+")",cont-1, 1);
            tabla.setValueAt(((visitados)?visited.toString():""), cont-1, 2);
            if(i.getaDerecha()!=null && i.getaIzquierda()!=null)
            {
               
                /**
                 * izquierda
                 */
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.push(new NodoCamino(0, i.getaIzquierda().getOrigen().getNombre()+i.getNombre(), temp));
                 /**
                 *  derecha
                 */
                 temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.push(new NodoCamino(0, i.getaDerecha().getOrigen().getNombre()+i.getNombre(), temp));
                /**
                 * Como es una pila con esto nos aseguramos de que el de la izquierda siempre sea el primer elemento.
                 */
               if(visitados)
               {
                   this.visited.add(i.getaDerecha().getOrigen());
                   this.visited.add(i.getaIzquierda().getOrigen());
               }
               return primeroProfundidad(visitados, i, f, ex);
                
            }
            if(i.getaDerecha()==null && i.getaIzquierda()!=null)
            {
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(0, i.getaIzquierda().getOrigen().getNombre()+i.getNombre(), temp));
                if(visitados)
               {
                   this.visited.add(i.getaIzquierda().getOrigen());
               }
                return primeroProfundidad(visitados, i, f, ex);
            }
            if(i.getaDerecha()!=null && i.getaIzquierda()==null)
            {
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(0, i.getaDerecha().getOrigen().getNombre()+i.getNombre(), temp));
               if(visitados)
               {
                   this.visited.add(i.getaDerecha().getOrigen());
               }
                return primeroProfundidad(visitados, i, f, ex);
            }
            if(i.getaDerecha()!=null && i.getaIzquierda()==null)
            {
                JOptionPane.showMessageDialog(null, "Error, el nodo inicial debe de tener almenos una arista ","",JOptionPane.ERROR_MESSAGE);
                return 0;
            }
        }
        else
        {
            cont++;
            NodoCamino frimero= ex.peek();
            Nodo toExp= frimero.NodosCamino.get(frimero.NodosCamino.size()-1);
            String nod="";
            for (int j = ex.size()-1; j >= 0; j--) {
                nod+=" ("+ex.get(j).NombreCamino+") ";
            }
             tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(), cont-1, 0);
            tabla.setValueAt(nod, cont-1, 1);
            tabla.setValueAt(((visitados)?visited.toString():""), cont-1, 2);
            if(toExp.getaDerecha()!=null && toExp.getaIzquierda()!=null)
            {
                /**Izquierda*/
                temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                if(visitados){
                      if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                            ex.push(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                }
                else
                    ex.push(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                
                /**Derecha*/
                temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaDerecha().getOrigen());
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        ex.push(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
                
                }
                else
                    ex.push(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
               
                ex.remove(frimero);
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        this.visited.add(toExp.getaDerecha().getOrigen());
                    if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        this.visited.add(toExp.getaIzquierda().getOrigen());
                }
                return primeroProfundidad(visitados, i, f, ex);
            }
            if(toExp.getaDerecha()==null && toExp.getaIzquierda()!=null)
            {
                temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                if(visitados){
                      if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                            ex.push(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                }
                else
                    ex.push(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                
                ex.remove(frimero); 
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        this.visited.add(toExp.getaIzquierda().getOrigen());
                }
                 return primeroProfundidad(visitados, i, f, ex);
            }
            if(toExp.getaDerecha()!=null && toExp.getaIzquierda()==null)
            {
                 temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaDerecha().getOrigen());
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        ex.push(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
                
                }
                else
                    ex.push(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
                 ex.remove(frimero); 
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        this.visited.add(toExp.getaDerecha().getOrigen());
                }
                 return primeroProfundidad(visitados, i, f, ex);
            }
            if(toExp.getaDerecha()==null && toExp.getaIzquierda()==null)
            {
                if(toExp==f)
                    return 1;
                else
                {
                    ex.remove(frimero);
                    return primeroProfundidad(visitados, i, f, ex);
                }
            }
        }
        return 0;
    }
    
    private int primeroAnchura(boolean visitados,Nodo i, Nodo f, ArrayList<NodoCamino> ex)
    {
        if(ex==null)
        {
            this.cont=1;
            ex= new ArrayList<NodoCamino>();
            if(visitados)
            {
                visited= new VisitiadosExpandidos();
                visited.add(i);
            }
            tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt("("+i.getNombre()+")",cont-1, 1);
            tabla.setValueAt(((visitados)?visited.toString():""), cont-1, 2);
            if(i.getaDerecha()!=null && i.getaIzquierda()!=null)
            { 
                /**
                 *  derecha
                 */
                 temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(0, i.getaDerecha().getOrigen().getNombre()+i.getNombre(), temp));
                /**
                 * izquierda
                 */
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(0, i.getaIzquierda().getOrigen().getNombre()+i.getNombre(), temp));
                 if(visitados)
               {
                   this.visited.add(i.getaDerecha().getOrigen());
                   this.visited.add(i.getaIzquierda().getOrigen());
               }
               return primeroAnchura(visitados, i, f, ex);
                
            }
            if(i.getaDerecha()==null && i.getaIzquierda()!=null)
            {
                 /**
                 * izquierda
                 */
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(0, i.getaIzquierda().getOrigen().getNombre()+i.getNombre(), temp));
                if(visitados)
               {
                   this.visited.add(i.getaIzquierda().getOrigen());
               }
               return primeroAnchura(visitados, i, f, ex);
            }
            if(i.getaDerecha()!=null && i.getaIzquierda()==null)
            {
                /**
                 *  derecha
                 */
                 temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(0, i.getaDerecha().getOrigen().getNombre()+i.getNombre(), temp));
                 if(visitados)
               {
                   this.visited.add(i.getaDerecha().getOrigen());
               }
               return primeroAnchura(visitados, i, f, ex);
            }
            if(i.getaDerecha()==null && i.getaIzquierda()==null)
            {
                JOptionPane.showMessageDialog(null, "Error, el nodo inicial debe de tener almenos una arista ","",JOptionPane.ERROR_MESSAGE);
                return 0;
            }
        }
        else{
            cont++;
              NodoCamino frimero= ex.get(0);
              Nodo toExp= frimero.NodosCamino.get(frimero.NodosCamino.size()-1);
              String nod="";
              for (NodoCamino nodoCamino : ex) {
                nod+= " ("+nodoCamino.NombreCamino+") ";
            }
               tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(), cont-1, 0);
            tabla.setValueAt(nod, cont-1, 1);
            tabla.setValueAt(((visitados)?visited.toString():""), cont-1, 2);
             if(toExp.getaDerecha()!=null && toExp.getaIzquierda()!=null)
            {
                /**Derecha*/
                temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaDerecha().getOrigen());
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        ex.add(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
                
                }
                else
                    ex.add(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
                //Izquierda
                 temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                if(visitados){
                      if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                            ex.add(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                }
                else
                    ex.add(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                ex.remove(frimero);
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        this.visited.add(toExp.getaDerecha().getOrigen());
                    if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        this.visited.add(toExp.getaIzquierda().getOrigen());
                }
                 return primeroAnchura(visitados, i, f, ex);
            }
             if(toExp.getaDerecha()==null && toExp.getaIzquierda()!=null)
            {
                  temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                if(visitados){
                      if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                            ex.add(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                }
                else
                    ex.add(new NodoCamino(0, toExp.getaIzquierda().getOrigen().getNombre()+frimero.NombreCamino, temp));
                ex.remove(frimero);
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        this.visited.add(toExp.getaIzquierda().getOrigen());
                }
                 return primeroAnchura(visitados, i, f, ex);
            }
             if(toExp.getaDerecha()!=null && toExp.getaIzquierda()==null)
            {
                         temp= new ArrayList<Nodo>();
                for (int j = 0; j < frimero.NodosCamino.size(); j++) {
                    temp.add(frimero.NodosCamino.get(j));
                }
                temp.add(toExp.getaDerecha().getOrigen());
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        ex.add(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
                
                }
                else
                    ex.add(new NodoCamino(0, toExp.getaDerecha().getOrigen().getNombre()+frimero.NombreCamino, temp));
                ex.remove(frimero);
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        this.visited.add(toExp.getaDerecha().getOrigen());
                }
                 return primeroAnchura(visitados, i, f, ex);
                
            }
             if(toExp.getaDerecha()==null && toExp.getaIzquierda()==null)
            {
                if(toExp==f)
                    return 1;
                else
                {
                    ex.remove(frimero);
                    return primeroAnchura(visitados, i, f, ex);
                }
            }
        }
        return 0;
    }
    
    private int primeroElMejor(boolean visitados, Nodo i, Nodo f, ArrayList<NodoCamino> ex)
    {
        if(ex==null)
        {
            cont=1;
            ex= new ArrayList<NodoCamino>();
            if(visitados)
            {
                visited= new VisitiadosExpandidos();
                visited.add(i);
            }
           tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt("("+i.getNombre()+")",cont-1, 1);
            tabla.setValueAt(((visitados)?visited.toString():""), cont-1, 2);
            if(i.getaDerecha()!=null&& i.getaIzquierda()!=null)
            {
                temp = new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(i.getaDerecha().getOrigen().getValorHeuristico(), i.getaDerecha().getOrigen().getNombre()+i.getNombre(),temp));
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(i.getaIzquierda().getOrigen().getValorHeuristico(), i.getaIzquierda().getOrigen().getNombre()+i.getNombre(),temp));
               if(visitados)
               {
                   if(this.visited.indexOf(i.getaDerecha().getOrigen())<0)
                        this.visited.add(i.getaDerecha().getOrigen());
                   if(this.visited.indexOf(i.getaIzquierda().getOrigen())<0)
                        this.visited.add(i.getaIzquierda().getOrigen());
               }
                return primeroElMejor(visitados,i, f, ex);
            }
            if(i.getaDerecha()==null&& i.getaIzquierda()!=null)
            {
                 temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(i.getaIzquierda().getOrigen().getValorHeuristico(), i.getaIzquierda().getOrigen().getNombre()+i.getNombre(),temp));
                  if(visitados)
               {
                   if(this.visited.indexOf(i.getaIzquierda().getOrigen())<0)
                        this.visited.add(i.getaIzquierda().getOrigen());
               }
              return primeroElMejor(visitados,i, f, ex);
            }
            if(i.getaDerecha()!=null&& i.getaIzquierda()==null)
            {
                 temp = new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(i.getaDerecha().getOrigen().getValorHeuristico(), i.getaDerecha().getOrigen().getNombre()+i.getNombre(),temp));
                if(visitados)
               {
                   if(this.visited.indexOf(i.getaDerecha().getOrigen())<0)
                        this.visited.add(i.getaDerecha().getOrigen());
               }
                return primeroElMejor(visitados,i, f, ex);
            }
            if(i.getaDerecha()==null&& i.getaIzquierda()==null)
            {
                 JOptionPane.showMessageDialog(null, "Error, el nodo inicial debe de tener almenos una arista ","",JOptionPane.ERROR_MESSAGE);
                return 0;
            }
        }
        else
        {
            cont++;
            String nod="";
             NodoCamino nMenor= ex.get(0);
             for (int j = 0; j < ex.size(); j++) {
                 nod+=" ("+ex.get(j).ValorCamino+ex.get(j).NombreCamino+") ";
                if(ex.get(j).ValorCamino< nMenor.ValorCamino)
                    nMenor=ex.get(j);
            }
             tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt(nod,cont-1, 1);
            tabla.setValueAt(((visitados)?visited.toString():""), cont-1, 2);
            Nodo toExp= nMenor.NodosCamino.get(nMenor.NodosCamino.size()-1);
            if(toExp.getaDerecha()!=null&& toExp.getaIzquierda()!=null)
            {
                /**Derecha*/
                temp= new ArrayList<Nodo>();
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                temp.add(toExp.getaDerecha().getOrigen());
                if(visitados)
                {
                    if(visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        ex.add(new NodoCamino(toExp.getaDerecha().getOrigen().getValorHeuristico(), toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino, temp)); 
                }
                else
                    ex.add(new NodoCamino(toExp.getaDerecha().getOrigen().getValorHeuristico(), toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino, temp));
                /**Izquierda*/
                 temp= new ArrayList<Nodo>();
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                if(visitados)
                {
                    if(visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        ex.add(new NodoCamino(toExp.getaIzquierda().getOrigen().getValorHeuristico(), toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino, temp)); 
                }
                else
                    ex.add(new NodoCamino(toExp.getaIzquierda().getOrigen().getValorHeuristico(), toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino, temp));
                ex.remove(nMenor);
                if(visitados)
                {
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        this.visited.add(toExp.getaDerecha().getOrigen());
                    if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        this.visited.add(toExp.getaIzquierda().getOrigen());
                }
               return primeroElMejor(visitados,i, f, ex);
                
            }
            if(toExp.getaDerecha()==null&& toExp.getaIzquierda()!=null)
            {
                 temp= new ArrayList<Nodo>();
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                if(visitados)
                {
                    if(visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        ex.add(new NodoCamino(toExp.getaIzquierda().getOrigen().getValorHeuristico(), toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino, temp)); 
                }
                else
                    ex.add(new NodoCamino(toExp.getaIzquierda().getOrigen().getValorHeuristico(), toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino, temp));
                ex.remove(nMenor);
                if(visitados)
                {
                    
                    if(this.visited.indexOf(toExp.getaIzquierda().getOrigen())<0)
                        this.visited.add(toExp.getaIzquierda().getOrigen());
                }
                return primeroElMejor(visitados,i, f, ex);
            }
            if(toExp.getaDerecha()!=null&& toExp.getaIzquierda()==null)
            {
                 temp= new ArrayList<Nodo>();
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                temp.add(toExp.getaDerecha().getOrigen());
                if(visitados)
                {
                    if(visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        ex.add(new NodoCamino(toExp.getaDerecha().getOrigen().getValorHeuristico(), toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino, temp)); 
                }
                else
                    ex.add(new NodoCamino(toExp.getaDerecha().getOrigen().getValorHeuristico(), toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino, temp));
                 if(visitados)
                {
                    
                    if(this.visited.indexOf(toExp.getaDerecha().getOrigen())<0)
                        this.visited.add(toExp.getaDerecha().getOrigen());
                }
                return primeroElMejor(visitados,i, f, ex);
      
            }
            if(toExp.getaDerecha()==null&& toExp.getaIzquierda()==null)
            {
                if(f== toExp)
                    return 1;
                else
                {
                    ex.remove(nMenor);
                    return primeroElMejor(visitados,i, f, ex);
                }
            }
        }
        return 0;
    }
    
    public int aEstrella (Nodo f,Nodo i, ArrayList<NodoCamino> ex)
    {
        if(ex==null)
        {
            cont=1;
            ex= new ArrayList<NodoCamino>();
            tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt("("+i.getNombre()+")",cont-1, 1);
            //System.out.println("("+i.getNombre()+")");
            if(i.getaDerecha()!=null&& i.getaIzquierda()!=null)
            {
                temp = new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(i.getaDerecha().getValorCamino()+i.getaDerecha().getOrigen().getValorHeuristico(), i.getaDerecha().getOrigen().getNombre()+i.getNombre(),temp));
                temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(i.getaIzquierda().getValorCamino()+i.getaIzquierda().getOrigen().getValorHeuristico(), i.getaIzquierda().getOrigen().getNombre()+i.getNombre(),temp));
                return  aEstrella(f, i, ex);
            }
            if(i.getaDerecha()==null&& i.getaIzquierda()!=null)
            {
                 temp= new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaIzquierda().getOrigen());
                ex.add(new NodoCamino(i.getaIzquierda().getValorCamino()+ i.getaIzquierda().getOrigen().getValorHeuristico(), i.getaIzquierda().getOrigen().getNombre()+i.getNombre(),temp));
                return  aEstrella(f, i, ex);
            }
            if(i.getaDerecha()!=null&& i.getaIzquierda()==null)
            {
                temp = new ArrayList<Nodo>();
                temp.add(i);
                temp.add(i.getaDerecha().getOrigen());
                ex.add(new NodoCamino(i.getaDerecha().getValorCamino()+i.getaDerecha().getOrigen().getValorHeuristico(), i.getaDerecha().getOrigen().getNombre()+i.getNombre(),temp));
                return  aEstrella(f, i, ex);
            }
            if(i.getaDerecha()==null&& i.getaIzquierda()==null)
            {
                JOptionPane.showMessageDialog(null, "Error, el nodo inicial debe de tener almenos una arista ","",JOptionPane.ERROR_MESSAGE);
                return 0;
            }
            
        }
        else
        {
            NodoCamino nMenor= ex.get(0);
            cont++;
            String nombre="";
            for (NodoCamino nodoCamino : ex) {
                nombre+=" ("+nodoCamino.ValorCamino+nodoCamino.NombreCamino+") ";
                if(nMenor.ValorCamino>=nodoCamino.ValorCamino)
                {   
                    if(nMenor.NodosCamino.get(nMenor.NodosCamino.size()-1) != f)
                        nMenor= nodoCamino;
                }
                
            }
             tabla.addRow(new Object[] {"","",""});
            tabla.setValueAt(cont.toString(),cont-1, 0);
            tabla.setValueAt(nombre,cont-1, 1);
            Nodo toExp= nMenor.NodosCamino.get(nMenor.NodosCamino.size()-1);
            if(toExp.getaDerecha()!=null && toExp.getaIzquierda()!=null)
            {
                temp= new ArrayList<Nodo>();
                valor=0;
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                //Se agrega la expansion de la derecha
                temp.add(toExp.getaDerecha().getOrigen());
                //Se calcula el valor de la expansion de la derecha
                valor= nMenor.ValorCamino+ toExp.getaDerecha().getValorCamino()-toExp.getValorHeuristico()+toExp.getaDerecha().getOrigen().getValorHeuristico();
                //Se agrega la expansion a la lista de nodos expandidos
                ex.add(new NodoCamino(valor, toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                /*Ahora vamos con la izquierda*/
                temp= new ArrayList<Nodo>();
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                temp.add(toExp.getaIzquierda().getOrigen());
                valor=nMenor.ValorCamino +toExp.getaIzquierda().getValorCamino()-toExp.getValorHeuristico()+toExp.getaIzquierda().getOrigen().getValorHeuristico();
                ex.add(new NodoCamino(valor, toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                //Una vez finalizamos la expasion de los nodos eliminamos el camino anterior de la lista de expandidos
                ex.remove(nMenor);
                //Se vuelve a llamar a la funcion
                  return  aEstrella(f, i, ex);
            }
            if(toExp.getaDerecha()==null && toExp.getaIzquierda()!=null)
            {
                 temp= new ArrayList<Nodo>();
                valor=0;
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                //Se agrega la expansion de la derecha
                temp.add(toExp.getaIzquierda().getOrigen());
                //Se calcula el valor de la expansion de la derecha
                valor= nMenor.ValorCamino+ toExp.getaIzquierda().getValorCamino()-toExp.getValorHeuristico()+toExp.getaIzquierda().getOrigen().getValorHeuristico();
                //Se agrega la expansion a la lista de nodos expandidos
                ex.add(new NodoCamino(valor, toExp.getaIzquierda().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                ex.remove(nMenor);
                //Se vuelve a llamar a la funcion
                  return  aEstrella(f, i, ex);
            }
            if(toExp.getaDerecha()!=null && toExp.getaIzquierda()==null)
            {
                temp= new ArrayList<Nodo>();
                valor=0;
                for (int j = 0; j < nMenor.NodosCamino.size(); j++) {
                    //Agregamos los nodos anteriores
                    temp.add(nMenor.NodosCamino.get(j));
                }
                //Se agrega la expansion de la derecha
                temp.add(toExp.getaDerecha().getOrigen());
                //Se calcula el valor de la expansion de la derecha
                valor= nMenor.ValorCamino+ toExp.getaDerecha().getValorCamino()-toExp.getValorHeuristico()+toExp.getaDerecha().getOrigen().getValorHeuristico();
                //Se agrega la expansion a la lista de nodos expandidos
                ex.add(new NodoCamino(valor, toExp.getaDerecha().getOrigen().getNombre()+nMenor.NombreCamino,temp));
                ex.remove(nMenor);
                //Se vuelve a llamar a la funcion
                 return  aEstrella(f, i, ex);
            }
            if(toExp.getaDerecha()==null && toExp.getaIzquierda()==null)
            {
                if(toExp==f)
                    return 1;
                else{
                    //Si no hay nada que expander y toExp no es la meta entonces el camino se elmina
                    //y se una vez se encuentra el camino eliminado se vuelve a
                    //preguntar cual es el nuevo camino mas corto
                    ex.remove(nMenor);
                    return aEstrella(f, i, ex);
                }
            }
        }
        return 0;
    }
  

     DefaultTableModel tabla = null;
    public void ejecutarBusqueda(int tipoAlgoritmo)
    {
        this.tabla =(DefaultTableModel) ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).TablaBusqueda.getModel();
        boolean ve= ((Inicio)((JRootPane)(((JLayeredPane)(((JPanel)this.getParent()).getParent())).getParent())).getParent()).VisitadosExpandidosCheckbox.isSelected();
        Nodo i = this.getNodoInicial();
        Nodo f = this.getNodoFinal();
        switch(tipoAlgoritmo)
        {
            case 1:
                if(i!=null && f!=null)
                {
                 costoUniformeAlg(f, i, null);
                }
                break;
            case 2:
                if(i!=null && f!=null)
                {
                    primeroProfundidad(ve, i, f, null);
                }
                break;
            case 3:
                 if(i!=null && f!=null)
                {
                    primeroAnchura(ve, i, f, null);
                }
                break;
            case 4:
                 if(i!=null && f!=null)
                {
                    primeroElMejor(ve, i, f, null);
                }
                break;
            case 5:
                  if(i!=null && f!=null)
                {
                    aEstrella(f, i, null);
                }
                break;
        }
    }
}
 class NodoDireccion
{
    Nodo n;
    int direccion;

    public NodoDireccion(Nodo n, int direccion) {
        this.n = n;
        this.direccion = direccion;
    }
   
}

 class NodoCamino
    {
           int ValorCamino=0;
           String NombreCamino="";
           ArrayList<Nodo> NodosCamino=null;
        
        public NodoCamino(int v,String na,ArrayList<Nodo> n)
        {
            this.ValorCamino=v;
            this.NombreCamino=na;
            this.NodosCamino=n;
        }
    }
